function bvqxtools_postinstall
% bvqxtools_postinstall  - post installation tasks
%
% FORMAT:       bvqxtools_postinstall
%
% No input/output fields.

% Version:  v0.8a
% Build:    9102316
% Date:     Oct-23 2009, 4:46 PM CEST
% Author:   Jochen Weber, SCAN Unit, Columbia University, NYC, NY, USA
% URL/Info: http://wiki.brainvoyager.com/BVQXtools

% clear classes first
evalin('base', 'clear classes;', '');
evalin('base', 'rehash toolboxcache;', '');
evalin('base', 'rehash;', '');

% get current pwd and switch..
opwd = cd;
cd(bvqxtools_path);

try
    rs = get(0, 'ScreenSize');
    if all(rs(3:4) >= [640, 480])
        hFig = BVQXfigure( ...
            [bvqxtools_path('tfg') '/bvqxtools_postinstall.tfg']);
        hPrg = hFig.TagStruct.LB_Progress;
        hBar = hFig.TagStruct.PB_Progress;
    else
        hPrg = [];
        hBar = [];
    end
catch
    warning( ...
        'BVQXtools:BVQXfigureError', ...
        'Error with BVQXfigure class: %s.', ...
        lasterr ...
    );
    hPrg = [];
    hBar = [];
end

% print banner
bvqxtv = bvqxtools_version;
bvqxtb = sprintf('%d', bvqxtools_build);
if exist('bvqxtools_private.m', 'file') == 2 && ...
    eval('bvqxtools_private', 'false')
    vtype = 'private';
    vbann = [ ...
        char(10), ...
        ' *** THIS IS A PRIVATE COPY OF THE BVQXtools TOOLBOX ***', char(10), ...
        ' *** DO NOT SHARE THIS INSTALLATION WITH OTHER USERS ***', char(10)];
else
    vtype = 'public';
    vbann = '';
end
banner = [ ...
    char(10), ...
    char(10), ...
    char(10), ...
    '==========================================================', char(10), ...
    char(10), ...
    ' BVQXtools v' bvqxtv ', build ' bvqxtb ' (' vtype ' edition)', char(10), ...
    char(10), ...
    ' Please direct any bug reports and/or feature requests', char(10), ...
    ' directly to the main author and maintainer:', char(10), ...
    char(10), ...
    ' Jochen Weber <jw2661@columbia.edu>', char(10), ...
    vbann, ...
    char(10), ...
    ' Thanks must go to Chih-Jen Lin for allowing the re-use of', char(10), ...
    ' the libSVM code repository :)', char(10), ...
    char(10), ...
    '==========================================================', char(10), ...
    char(10)];
instprog(hPrg, hBar, banner, 0.05);

% build libs (MEX)
try
    instprog(hPrg, hBar, 'Creating MEX files for current platform...', 0.05, ...
        'Compiling MEX files...');
    bvqxtools_makelibs(hPrg, hBar, [0.05, 0.5]);
    
% if an error occurred
catch
    
    % try copying fissing files
    mxt = mexext;
    mxs = strrep(mxt, 'mex', '');
    compfld = [bvqxtools_path('files') filesep 'compiled' filesep mxs filesep];
    cfiles = strrep(findfiles(bvqxtools_path, '*.c'), '.c', ['.' mexext]);
    nffiles = zeros(1, numel(cfiles));
    for nc = 1:numel(cfiles)
        if exist(cfiles{nc}, 'file') ~= 3
            [cfilf, cfile] = fileparts(cfiles{nc});
            if exist([compfld cfile], 'file') == 2
                if cpfile([compfld cfile], cfiles{nc}) ~= 1
                    nffiles(nc) = 2;
                else
                    nffiles(nc) = 1;
                end
            else
                nffiles(nc) = 2;
            end
        end
    end
    notcomp = sum(nffiles > 0);
    notavail = sum(nffiles > 1);
    if notcomp > 0
        instprog(hPrg, hBar, ...
            'Some MEX file(s) weren''t correctly compiled on your platform.');
        if notavail > 0
            disp(sprintf(['The following MEX files are not available on ' ...
                'your platform:\n%s\n\nTry downloading http://bvqxtools.' ...
                'cjhammond.com/BVQXtools_v%s_%s.zip, and unpack missing ' ...
                'files into %s.\n\n. Please contact the author if you ' ...
                'run into problems.'], sprintf('\n - %s', cfiles{nffiles > 1}), ...
                bvqxtv, mexext, bvqxtools_path));
        else
            disp([ ...
            'Those were copied from the files distribution directory.', char(10), ...
            'If you run into problems, please contact the author for help.']);
        end
    end
end

% if necessary try chmodding the executable
if ~ispc
    eval(['!chmod 755 ' strrep(bvqxtools_path('files'), ' ', '\ ') ...
        '/bin/' strrep(mexext, 'mex', '') '/*'], '');
end

% swap image
try
    if ~isempty(hPrg)
        oldi = hFig.TagStruct.IM_Splash.CData;
        newi = imread([bvqxtools_path('images') '/splash2.jpg']);
        for blendc = 1/32:1/32:1
            hFig.TagStruct.IM_Splash.CData = uint8(round( ...
                blendc .* double(newi) + (1 - blendc) .* double(oldi)));
            drawnow;
        end
    end
catch
    % do nothing
end

% check "helper classes"
try
    instprog(hPrg, hBar, 'Checking BVQXinifile class...', 0.5, 'Checking classes...');
    v = BVQXinifile;
    if ~isBVQXinifile(v)
        error('CLASS_FAILURE');
    end
catch
    warning( ...
        'BVQXtools:BVQXinifileError', ...
        'Error with BVQXinifile class: %s.', ...
        lasterr ...
    );
end

% check BVQXfile and build cached formats info
try
    instprog(hPrg, hBar, '(Re-)Creating BVQXfile cached information...', 0.52);
    try
        cachefile = [bvqxtools_path '/@BVQXfile/cache/cache.mat'];
        if exist(cachefile, 'file') == 2
            delete(cachefile);
        end
    catch
        % do nothing
    end
    v = BVQXfile;
    x = sort(fieldnames(v.Extensions));
    nx = numel(x);
    if mod(nx, 8) > 0
        x(end+1:8 * ceil(nx / 8)) = {''};
    end
    x8 = cell(1, numel(x) / 8);
    for xc = 1:numel(x8)
        x8{xc} = sprintf('%5s ', x{(xc - 1) * 8 + 1:xc*8});
    end
    info = [char(10), ...
        sprintf('Current release supports %d BVQX filetypes:', nx), char(10), ...
    	char(10), ...
        upper(gluetostring(x8, char(10))), char(10)];
    instprog(hPrg, hBar, info, 0.75);
catch
    warning( ...
        'BVQXtools:BVQXfileError', ...
        'Error creating/loading cached info for BVQXfile class: %s.', ...
        lasterr ...
    );
end

% create colin brain vmr from colin and mask
try
    instprog(hPrg, hBar, 'Masking colin.vmr -> colin_brain.vmr...', 0.75, ...
        'Patching/creating required binary files');
    vmrs = cell(1, 2);
    vmrs{1} = BVQXfile([bvqxtools_path('colin'), filesep, 'colin.vmr']);
    vmrs{2} = BVQXfile([bvqxtools_path('colin'), filesep, 'brainmask.vmr']);
    if istransio(vmrs{1}.VMRData)
        vmrs{1}.VMRData = resolve(vmrs{1}.VMRData);
    end
    if istransio(vmrs{2}.VMRData)
        vmrs{2}.VMRData = resolve(vmrs{2}.VMRData);
    end
    instprog(hPrg, hBar, '', 0.77);
    vmrs{2}.VMRData(vmrs{2}.VMRData == 255) = ...
        vmrs{1}.VMRData(vmrs{2}.VMRData == 255);
    instprog(hPrg, hBar, '', 0.78);
    vmrs{2}.SaveAs([bvqxtools_path('colin'), filesep, 'colin_brain.vmr']);
    clearbvqxobjects(vmrs);
catch
    clearbvqxobjects(vmrs);
    warning( ...
        'BVQXtools:BVQXfileError', ...
        'Error creating colin_brain.vmr: %s.', ...
        lasterr ...
    );
end

% creating colin SPH files
try
    instprog(hPrg, hBar, 'Creating colin_LH_SPH.srf and colin_RH_SPH.srf ...', 0.8);
    load([bvqxtools_path('colin'), filesep, 'colin_sph.mat']);
    load([bvqxtools_path('srf'), filesep, 'sph80.mat']);
    instprog(hPrg, hBar, '', 0.82);
    hemi = BVQXfile('new:srf');
    hemi.ExtendedNeighbors = 0;
    hemi.NrOfVertices = 40962;
    hemi.NrOfTriangles = 81920;
    hemi.MeshCenter = [128, 128, 128];
    hemi.VertexCoordinate = colin_sph.LH.VertexCoordinate;
    hemi.VertexNormal = zeros(40962, 3);
    hemi.ConvexRGBA = colin_sph.ConvexRGBA;
    hemi.ConcaveRGBA = colin_sph.ConcaveRGBA;
    hemi.VertexColor = [colin_sph.LH.VertexColor1, zeros(40962, 3)];
    instprog(hPrg, hBar, '', 0.83);
    [hemi.Neighbors, skip] = bvqx_srf_parseneighborsc( ...
        [sph80.Neighbors, uint32(zeros(1, 16))], 40962);
    hemi.TriangleVertex = sph80.TriangleVertex;
    hemi.NrOfTriangleStrips = 0;
    hemi.TriangleStripSequence = zeros(0, 1);
    hemi.AutoLinkedMTC = '';
    hemi.RecalcNormals;
    instprog(hPrg, hBar, '', 0.84);
    hemi.SaveAs([bvqxtools_path('colin'), filesep, 'colin_LH_SPH.srf']);
    instprog(hPrg, hBar, '', 0.86);
    hemi.VertexCoordinate = colin_sph.RH.VertexCoordinate;
    hemi.VertexColor(:, 1) = colin_sph.RH.VertexColor1;
    hemi.RecalcNormals;
    instprog(hPrg, hBar, '', 0.87);
    hemi.SaveAs([bvqxtools_path('colin'), filesep, 'colin_RH_SPH.srf']);
    hemi.ClearObject;
catch
    warning( ...
        'BVQXtools:BVQXfileError', ...
        'Error creating colin_xH_SPH.srf file/s: %s.', ...
        lasterr ...
    );
end

% create tdlocal files
instprog(hPrg, hBar, '', 0.88);
try
    if strcmpi(vtype, 'private')
        instprog(hPrg, hBar, 'Creating tdlocal cached database file...', ...
            0.88, 'Creating some private files');
        tdlocal(2, 0, 0, 0);
    end
catch
    warning( ...
        'BVQXtools:TDLocalError', ...
        'Error using tdlocal: %s.', ...
        lasterr ...
    );
end

% create tdlocal2 files
try
    instprog(hPrg, hBar, 'Creating tdlocal2 cached database file...', ...
        0.89, 'Hashing tdlocal2 database');
    tdlocal2(2, 0, 0, 0);
catch
    warning( ...
        'BVQXtools:TDLocalError', ...
        'Error using tdlocal2: %s.', ...
        lasterr ...
    );
end

% check UI class
instprog(hPrg, hBar, 'Checking BVQXtool UI class...', 0.94, 'Checking UI class');
try
    BVQXtool;
    instprog(hPrg, hBar, '', 0.98);
    BVQXtool(0, 'close', true);
catch
    warning( ...
        'BVQXtools:BVQXtoolError', ...
        'Error with BVQXtool UI class: %s.', ...
        lasterr ...
    );
end

% try to add path
try
    addpath(bvqxtools_path);
    savepath;
catch
    % do nothing
end

% clean up...
instprog(hPrg, hBar, 'Done.', 1, 'Cleaning up...');
pause(1);
if ~isempty(hPrg)
    disp(gluetostring(hPrg.String, char(10)));
end
try
    BVQXfigure(BVQXfigure, 'DeleteAllFigures');
catch
    % do nothing
end

% switch back
try
    cd(opwd);
catch
    % do nothing
end

% clear classes
clear classes;
evalin('base', 'clear classes;', '');
evalin('base', 'rehash toolboxcache;', '');
evalin('base', 'rehash;', '');


% sub function for progress
function instprog(hedt, hbar, txt, p, ptxt)
if ~isempty(hedt)
    if ~isempty(txt)
        str = hedt.String;
        if ischar(str) && ...
            size(str, 1) > 1
            str = cellstr(str);
        elseif ischar(str)
            str = splittocell(str, char(10));
        end
        str = [str(:); lsqueeze(splittocell(txt, char(10)))];
        hedt.String = str;
        hedt.ListboxTop = max(1, numel(str) - 16);
    end
    if nargin > 4
        hbar.Progress(p, ptxt);
    elseif nargin > 3
        hbar.Progress(p);
    end
    drawnow;
else
    disp(txt);
end
